package org.example.ttms.entityClass.train;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import javafx.beans.property.IntegerProperty;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import org.example.ttms.controller.AddTicketController;
import org.example.ttms.controller.AddTripsController;
import org.example.ttms.customize.AddTicket;
import org.example.ttms.entityClass.ticket.Ticket;

import java.io.*;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.util.*;

public class Trips {
    private String id;
    private String tripsId;
    private int routeId;
    private Date goTime;
    private String speedTime;
    private int ticketAllNum;
    private int sellTicketNum = 0;
    private String status = "正常";//车次状态--晚点---早点---正常---出发---到达
    private List<String> ticketList = new ArrayList<>();

    public Trips() {
    }

    public Trips(String tripsId, int routeId, Date goTime, String speedTime, int ticketAllNum) {
        this.tripsId = tripsId;
        this.routeId = routeId;
        this.goTime = goTime;
        this.speedTime = speedTime;
        this.ticketAllNum = ticketAllNum;
        this.ticketList = AddTicketController.ticket.addTicket();
        this.id = goTime + " " + this.tripsId;
    }

    public StringProperty tripsIdStringProperty() {
        return new SimpleStringProperty(tripsId);
    }

    public IntegerProperty routerIdProperty() {
        return new SimpleIntegerProperty(routeId);
    }

    public StringProperty goTimeProperty() {
        SimpleDateFormat format = new SimpleDateFormat("yyyy年MM月dd日HH时mm分");
        String dateString = format.format(goTime);
        return new SimpleStringProperty(dateString);
    }

    public StringProperty speedTimeProperty() {
        return new SimpleStringProperty(speedTime);
    }

    public IntegerProperty ticketAllNumProperty() {
        return new SimpleIntegerProperty(ticketAllNum);
    }

    public IntegerProperty sellTicketNumProperty() {
        return new SimpleIntegerProperty(sellTicketNum);
    }

    public StringProperty statusProperty() {
        return new SimpleStringProperty(status);
    }

    public StringProperty departureProperty(String departure) {
        return new SimpleStringProperty(departure);
    }

    public StringProperty destinationProperty(String destination) {
        return new SimpleStringProperty(destination);
    }

    public StringProperty goTimeProperty2(String departure) {
        Route route = new Route();
        route = route.obtainRoute(this.routeId);
        int index = route.obtainStationIndex(departure);
        int time = obtainTime(route, index);
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(goTime);
        calendar.add(Calendar.MINUTE, time);
        SimpleDateFormat format = new SimpleDateFormat("yyyy年MM月dd日HH时mm分");
        String dateString = format.format(calendar.getTime());
        return new SimpleStringProperty(dateString);
    }

    public Date goTimeDate(String departure){
        Route route = new Route();
        route = route.obtainRoute(this.routeId);
        int index = route.obtainStationIndex(departure);
        int time = obtainTime(route, index);
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(goTime);
        calendar.add(Calendar.MINUTE, time);
        return calendar.getTime();
    }

    public StringProperty arrivalTimeProperty2(String destination) {
        Route route = new Route();
        route = route.obtainRoute(this.routeId);
        int index = route.obtainStationIndex(destination);
        int time = obtainTime(route, index);
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(goTime);
        calendar.add(Calendar.MINUTE, time);
        SimpleDateFormat format = new SimpleDateFormat("yyyy年MM月dd日HH时mm分");
        String dateString = format.format(calendar.getTime());
        return new SimpleStringProperty(dateString);
    }

    public Date arrivalDate(String destination){
        Route route = new Route();
        route = route.obtainRoute(this.routeId);
        int index = route.obtainStationIndex(destination);
        int time = obtainTime(route, index);
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(goTime);
        calendar.add(Calendar.MINUTE, time);
        return calendar.getTime();
    }

    public IntegerProperty businessProperty() {
        return new SimpleIntegerProperty(obtainTicketNum("商务座"));
    }

    public IntegerProperty firstProperty() {
        return new SimpleIntegerProperty(obtainTicketNum("一等座"));
    }

    public IntegerProperty secondProperty() {
        return new SimpleIntegerProperty(obtainTicketNum("二等座"));
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getTripsId() {
        return tripsId;
    }

    public void setTripsId(String tripsId) {
        this.tripsId = tripsId;
    }

    public int getRouteId() {
        return routeId;
    }

    public void setRouteId(int routeId) {
        this.routeId = routeId;
    }

    public Date getGoTime() {
        return goTime;
    }

    public void setGoTime(Date goTime) {
        this.goTime = goTime;
    }

    public String getSpeedTime() {
        return speedTime;
    }

    public void setSpeedTime(String speedTime) {
        this.speedTime = speedTime;
    }

    public int getTicketAllNum() {
        return ticketAllNum;
    }

    public void setTicketAllNum(int ticketAllNum) {
        this.ticketAllNum = ticketAllNum;
    }

    public int getSellTicketNum() {
        return sellTicketNum;
    }

    public void setSellTicketNum(int sellTicketNum) {
        this.sellTicketNum = sellTicketNum;
    }

    public String getStatus() {
        return status;
    }

    public void setStatus(String status) {
        this.status = status;
    }

    public List<String> getTicketList() {
        return ticketList;
    }

    public void setTicketList(List<String> ticketList) {
        this.ticketList = ticketList;
    }

    //添加车次
    public void addTrips(Trips trips) {
        ObjectMapper objectMapper = new ObjectMapper();
        String file = "src/main/java/org/example/ttms/file/trips.txt";
        try {
            String jsonString = objectMapper.writeValueAsString(trips);
            System.out.println("addTrips:" + jsonString);
            BufferedWriter writer = new BufferedWriter(new OutputStreamWriter
                    (new FileOutputStream(file, true)));
            writer.write(jsonString + "\n");
            writer.close();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    //给路线添加车次
    public void routeAddTrips(Integer routeId, String tripsId) {
        Route route = new Route();
        HashMap<Integer, Route> hashMap = route.obtainAllRoute();
        Route changeRoute = hashMap.get(routeId);
        List<String> tripsList = changeRoute.getTripsList();
        if (tripsList.contains(tripsId)) {
            return;
        }
        tripsList.add(tripsId);
        changeRoute.setTripsNum(changeRoute.getTripsNum() + 1);
        changeRoute.setTripsList(tripsList);
        route.storageRoute(FXCollections.observableArrayList(hashMap.values()));
    }

    //获取所有车次
    public List<Trips> obtainAllTrips() {
        List<Trips> list = new ArrayList<>();
        String file = "src/main/java/org/example/ttms/file/trips.txt";
        try {
            Scanner scan = new Scanner(new FileReader(file));
            while (scan.hasNextLine()) {
                String str = scan.nextLine();
                ObjectMapper objectMapper = new ObjectMapper();
                Trips trips = objectMapper.readValue(str, Trips.class);
                list.add(trips);
            }
        } catch (FileNotFoundException | JsonProcessingException e) {
            throw new RuntimeException(e);
        }
        return list;
    }

    //获取所有车次---key只有一个
    public HashMap<String, Trips> obtainAllTrips2() {
        HashMap<String, Trips> hashMap = new HashMap<>();
        String file = "src/main/java/org/example/ttms/file/trips.txt";
        try {
            Scanner scan = new Scanner(new FileReader(file));
            while (scan.hasNextLine()) {
                String str = scan.nextLine();
                ObjectMapper objectMapper = new ObjectMapper();
                Trips trips = objectMapper.readValue(str, Trips.class);
                hashMap.put(trips.tripsId, trips);
            }
        } catch (FileNotFoundException | JsonProcessingException e) {
            throw new RuntimeException(e);
        }
        return hashMap;
    }

    //获取所有车次---key为id
    public HashMap<String, Trips> obtainAllTrips3() {
        HashMap<String, Trips> hashMap = new HashMap<>();
        String file = "src/main/java/org/example/ttms/file/trips.txt";
        try {
            Scanner scan = new Scanner(new FileReader(file));
            while (scan.hasNextLine()) {
                String str = scan.nextLine();
                ObjectMapper objectMapper = new ObjectMapper();
                Trips trips = objectMapper.readValue(str, Trips.class);
                hashMap.put(trips.id, trips);
            }
        } catch (FileNotFoundException | JsonProcessingException e) {
            throw new RuntimeException(e);
        }
        return hashMap;
    }

    //获取所有车次号
    public List<String> obtainAllTripsId() {
        HashMap<String, Trips> hashMap = obtainAllTrips2();
        Set<String> set = new HashSet<>(hashMap.keySet());
        return new ArrayList<>(set);
    }

    //储存车次---覆盖
    public void storageTrips(ObservableList<Trips> observableList) {
        ObjectMapper objectMapper = new ObjectMapper();
        String file = "src/main/java/org/example/ttms/file/trips.txt";
        try {
            BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(
                    new FileOutputStream(file)));
            String jsonString = null;
            for (Trips trips : observableList) {
                jsonString = objectMapper.writeValueAsString(trips);
                writer.write(jsonString + "\n");
            }
            writer.close();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    //减去路线的车次数
    public void decreaseTripsNum(Trips trips) {
        //先判断是否有该车次的车在其他时候走这条路线
        List<Trips> list = obtainAllTrips();
        for (Trips tmp : list) {
            if (tmp.routeId == trips.routeId) {
                if (tmp.tripsId.equals(trips.tripsId) && !tmp.status.equals("到达")
                        && !tmp.id.equals(trips.id)) {
                    return;
                }
            }
        }

        Route route = new Route();
        HashMap<Integer, Route> hashMap = route.obtainAllRoute();
        route = hashMap.get(trips.routeId);
        route.setTripsNum(route.getTripsNum() - 1);
        List<String> tripsList = route.getTripsList();
        tripsList.remove(trips.tripsId);
        route.setTripsList(tripsList);
        hashMap.replace(trips.routeId, route);
        //保存数据
        route.storageRoute(FXCollections.observableArrayList(hashMap.values()));
    }

    //修改车次状态
    public void changeStatus(Trips trips, String status) {
        HashMap<String, Trips> hashMap = obtainAllTrips3();
        hashMap.get(trips.id).setStatus(status);
        storageTrips(FXCollections.observableArrayList(hashMap.values()));
    }

    //获取指定车次的指定票的剩余票
    public int obtainTicketNum(String type) {
        Ticket ticket = new Ticket();
        int count = 0;
        HashMap<String, Ticket> hashMap = ticket.obtainAllTicket();
        for (Map.Entry<String, Ticket> map : hashMap.entrySet()) {
            Ticket ticket1 = map.getValue();
            if (ticket1.getId().equals(this.id)) {
                if (ticket1.getType().equals(type) && !ticket1.getStatus().equals("已售出")) {
                    count++;
                }
            }
        }
        return count;
    }

    //获取指定车次的指定票的剩余票
    public Double obtainTicketPrice(String type) {
        Ticket ticket = new Ticket();
        HashMap<String, Ticket> hashMap = ticket.obtainAllTicket();
        for (Map.Entry<String, Ticket> map : hashMap.entrySet()) {
            if (map.getValue().getType().equals(type) && map.getValue().getId().equals(this.id)) {
                return map.getValue().getPrice();
            }
        }
        return 0.0;
    }

    //获取买票的车次
    public HashMap<String, Trips> obtainBuyTicketTrips(String departure, String destination, LocalDate date) {
        List<Trips> list = obtainAllTrips();
        HashMap<String, Trips> hashMap = new HashMap<>();
        Route route = new Route();
        for (Trips trips : list) {
            LocalDate localDate = trips.goTime.toInstant().atZone(java.time.ZoneId.systemDefault()).toLocalDate();
            if (!trips.getStatus().equals("出发") && !trips.getStatus().equals("到达")
                    && localDate.isEqual(date)) {
                List<String> stationList = route.obtainRoute(trips.routeId).getStationList();
                int count = 0;
                for (String str : stationList) {
                    if (count == 0) {
                        if (str.equals(departure)) {
                            count++;
                        }
                    } else if (count == 1) {
                        if (str.equals(destination)) {
                            count++;
                        }
                    }
                }
                if (count == 2) {
                    hashMap.put(trips.id, trips);
                }
            }
        }
        return hashMap;
    }

    //获取买票的车次---有座
    public HashMap<String, Trips> obtainBuyTicketTrips2(String departure, String destination, LocalDate date) {
        List<Trips> list = obtainAllTrips();
        HashMap<String, Trips> hashMap = new HashMap<>();
        Route route = new Route();
        for (Trips trips : list) {
            LocalDate localDate = trips.goTime.toInstant().atZone(java.time.ZoneId.systemDefault()).toLocalDate();
            if (!trips.getStatus().equals("出发") && !trips.getStatus().equals("到达") &&
                    trips.getTicketAllNum() - trips.getSellTicketNum() != 0 &&
                    localDate.isEqual(date)) {
                List<String> stationList = route.obtainRoute(trips.routeId).getStationList();
                int count = 0;
                for (String str : stationList) {
                    if (count == 0) {
                        if (str.equals(departure)) {
                            count++;
                        }
                    } else if (count == 1) {
                        if (str.equals(destination)) {
                            count++;
                        }
                    }
                }
                if (count == 2) {
                    hashMap.put(trips.id, trips);
                }
            }
        }
        return hashMap;
    }

    //获取买票的车次---有座--改签
    public HashMap<String, Trips> obtainBuyTicketTrips3(String departure, String destination) {
        List<Trips> list = obtainAllTrips();
        HashMap<String, Trips> hashMap = new HashMap<>();
        Route route = new Route();
        for (Trips trips : list) {
            LocalDate localDate = trips.goTime.toInstant().atZone(java.time.ZoneId.systemDefault()).toLocalDate();
            if (!trips.getStatus().equals("出发") && !trips.getStatus().equals("到达") &&
                    trips.getTicketAllNum() - trips.getSellTicketNum() != 0) {
                List<String> stationList = route.obtainRoute(trips.routeId).getStationList();
                int count = 0;
                for (String str : stationList) {
                    if (count == 0) {
                        if (str.equals(departure)) {
                            count++;
                        }
                    } else if (count == 1) {
                        if (str.equals(destination)) {
                            count++;
                        }
                    }
                }
                if (count == 2) {
                    hashMap.put(trips.id, trips);
                }
            }
        }
        return hashMap;
    }

    //获取开车时间
    public int obtainTime(Route route, int index) {
        String[] strings = speedTime.split("小时|分钟");
        int time = (Integer.parseInt(strings[0]) * 60 + Integer.parseInt(strings[1])) / (route.getStationNum() - 1)
                * (index - 1);
        if (this.status.contains("早点")) {
            String[] strings2 = this.status.split("早点|时|分");
            time -= (Integer.parseInt(strings2[1]) * 60 + Integer.parseInt(strings2[2]));
        } else if (this.status.contains("晚点")) {
            String[] strings2 = this.status.split("晚点|时|分");
            time += (Integer.parseInt(strings2[1]) * 60 + Integer.parseInt(strings2[2]));
        }
        return time;
    }

    //根据票id获取整个车次
    public Trips obtainTrips(String id){
        HashMap<String, Trips> hashMap = obtainAllTrips3();
        return hashMap.get(id);
    }

    //搜索车次
    public HashMap<String, Trips> searchTrips(String str, String type){
        HashMap<String, Trips> hashMap = new HashMap<>();
        List<Trips> list = obtainAllTrips();
        if(type.equals("车次号")){
            for(Trips trips : list){
                if(trips.tripsId.contains(str)){
                    hashMap.put(trips.id, trips);
                }
            }
        }
        else{
            for(Trips trips : list){
                if(String.valueOf(trips.routeId).equals(str)){
                    hashMap.put(trips.id, trips);
                }
            }
        }
        return hashMap;
    }
    //删除车次
    public void delTrips(Trips trips){
        HashMap<String, Trips> hashMap = obtainAllTrips3();
        hashMap.remove(trips.id);
        storageTrips(FXCollections.observableArrayList(hashMap.values()));
    }
}
